#include "LobbyStaging.h"
#include "LobbyStagingPrv.h"

#include "LobbyClient.h"
#include "LobbyConfig.h"
#include "LobbyGame.h"
#include "LobbyResource.h"
#include "LobbyScreen.h"
#include "LobbyTypes.h"
#include "RoutingLogic.h"
#include "StagingLogic.h"
#include "WONLobbyPrv.h"

#include "WONCommon/WriteBuffer.h"
#include "WONGUI/Container.h"

using namespace WONAPI;


///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::UpdateGameSummary()
{
	if(!IAmCaptain())
		return;

	NetLogic *aLogic = LobbyStagingPrv::GetNetLogic();
	LobbyGame *aGame = GetGame();

	if(aLogic!=NULL && aGame!=NULL)
		aLogic->NetUpdateGameSummary(aGame);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SetEveryoneUnready()
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SetEveryoneUnready();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SetGameInProgress(bool inProgress)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SetGameInProgress(inProgress);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::TryJoinGame(LobbyGame *theGame)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->TryJoinGame(theGame);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::TryHostGame()
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->TryHostGame();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::LeaveGame(bool confirm)
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->LeaveGame(confirm);
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::Logout(bool confirm)
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->Logout(confirm);
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
LobbyGame* LobbyStaging::GetGame()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->GetGame();
	else
		return NULL;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
LobbyClient* LobbyStaging::GetMyClient()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->GetMyClient();
	else
		return NULL;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
LobbyPlayer* LobbyStaging::GetMyPlayer()
{
	LobbyClient *aClient = GetMyClient();
	if(aClient!=NULL)
		return aClient->GetPlayer();
	else
		return NULL;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::IAmReady()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->IAmReady();
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::IAmCaptain()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mStagingLogic->IAmCaptain();
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::UpdateStartButton()
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->UpdateStartButton();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
unsigned short LobbyStaging::GetLobbyPort()
{
	return gLobbyData.get()?gLobbyData->mLobbyPort:0;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SetLobbyPort(unsigned short thePort)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mLobbyPort = thePort;
}


///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::StartFirewallDetect()
{
	if(gLobbyData.get()!=NULL)
	{
		gLobbyData->mFirewallTestDone = false;
		gLobbyData->mPublicAddr = IPAddr();
	}
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SetPublicAddr(const IPAddr &theAddr)
{
	if(gLobbyData.get())
		gLobbyData->mPublicAddr = theAddr;
}
	
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SetBehindFirewall(bool behindFirewall)
{
	if(gLobbyData.get())
	{
		gLobbyData->mBehindFirewall = behindFirewall;
		gLobbyData->mFirewallTestDone = true;
	}
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
IPAddr LobbyStaging::GetIPAddr(LobbyGameType theGameType)
{
	IPAddr anAddr;
	if(gLobbyData.get()!=NULL)
	{
		if(theGameType!=LobbyGameType_Lan && gLobbyData->mPublicAddr.IsValid() && !gLobbyData->mLobbyConfig->mUseLocalIP)
			anAddr = gLobbyData->mPublicAddr;
		else
			anAddr = IPAddr::GetLocalAddr();

		anAddr.SetThePort(gLobbyData->mLobbyPort);
	}

	return anAddr;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
IPAddr LobbyStaging::GetPublicAddr()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mPublicAddr;
	else
		return IPAddr();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::IsBehindFirewall()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mBehindFirewall;
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
bool LobbyStaging::IsFirewallTestDone()
{
	if(gLobbyData.get()!=NULL)
		return gLobbyData->mFirewallTestDone;
	else
		return false;
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SendReadyRequest(bool isReady)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SendReadyRequest(isReady);

}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SendStartGame()
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SendStartGame();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SendDissolveGame()
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SendStartGame();
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SendGameMessageToCaptain(const ByteBuffer *theMsg)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SendGameMessageToCaptain(theMsg);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::BroadcastGameMessage(const ByteBuffer *theMsg)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->BroadcastGameMessage(theMsg);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::SendGameMessageToClient(LobbyClient *theClient, const ByteBuffer *theMsg)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->SendGameMessageToClient(theClient,theMsg);
}

///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
void LobbyStaging::KickClient(LobbyClient *theClient, bool isBan)
{
	if(gLobbyData.get()!=NULL)
		gLobbyData->mStagingLogic->KickClient(theClient,isBan);
}
